package isnork.g2;

import java.awt.geom.Point2D;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.Random;
import java.util.Set;

import javax.naming.directory.DirContext;
import javax.swing.plaf.basic.BasicInternalFrameTitlePane.MaximizeAction;

import isnork.g2.utility.Utility;
import isnork.sim.GameObject;
import isnork.sim.Observation;
import isnork.sim.SeaLifePrototype;
import isnork.sim.GameObject.Direction;


public class BackToBoat implements Strategy {
	
	public static int TOTAL_ROUNDS = 480;
	public static double MAX = Double.MAX_VALUE;
	private static double utility;
	private static final Point2D BOAT = new Point2D.Double(0.0, 0.0);
	private Direction direction_to_boat;
	private int time_need;
	private int free_time;
	double safeDegree;
	double dangerPerCell;
	
	BackToBoat(G2Explorer diver)
	{
		this.safeDegree =diver.safeDegree;
		//this.safeDegree = ExplorerConfig.safeDegree;
		
		this.dangerPerCell=diver.dangerPerCell;	
	}
	
	
	@Override	
	public Map<Direction, Double> process(G2Explorer diver) {
		// TODO Auto-generated method stub
		
		Map<Direction,Double> utility_accumulatorExp = new HashMap<Direction,Double>();
		for(Direction d : Direction.values()){
			utility_accumulatorExp.put(d, 0.0);
		}
		//System.out.printf("ReturnToBoat process started\n");
		direction_to_boat = Utility.RelativeDirection(diver.location, BOAT);
		int min = (int)Math.min(Math.abs(diver.location.getX()),Math.abs(diver.location.getY()));
		int max = (int)Math.max(Math.abs(diver.location.getX()), Math.abs(diver.location.getY()));
		time_need = 3*min+2*(max-min);
		free_time = TOTAL_ROUNDS - diver.current_round - time_need;
		
		if (free_time>time_need+6)
		{
			return null; 
		}
		
		// when you are on boat and time left < 6, if you go diag, can't make it back 
		if (diver.location==BOAT && diver.current_round >= (TOTAL_ROUNDS-6)){
			return null;
			//Return to boat directly will take care of this part
		}

		if (free_time<=6){
			return null;
			//Return to boat directly will take care of this part
		}
		
		
		double r = time_need/free_time;
		utility = ExplorerConfig.BACK*diver.maxDanger*r;
					
		for(Direction d : Direction.values())
		{  
			if (d == direction_to_boat)
			{
				utility_accumulatorExp.put(d, utility);
			}
			else if (Math.abs(d.getDegrees()-direction_to_boat.getDegrees())==45)
			{
				utility_accumulatorExp.put(d, utility*ExplorerConfig.secondChoice);
			}
			else if (Math.abs(d.getDegrees()-direction_to_boat.getDegrees())==45)
			{
				utility_accumulatorExp.put(d, utility*ExplorerConfig.thirdChoice);
			}
		}
		
		return utility_accumulatorExp;
		
	}
}